/** * <copyright> * * Copyright (c) 2002-2006 IBM Corporation and others. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * IBM - Initial API and implementation * * </copyright> * * $Id: RoseEcoreBuilder.java,v 1.21 2008/12/22 14:26:15 emerks Exp $ */ package com.sap.emf.importer.moin.rose.builder; import java.util.ArrayList; import java.util.Collections; import java.util.Comparator; import java.util.HashMap; import java.util.HashSet; import java.util.Iterator; import java.util.List; import java.util.ListIterator; import java.util.Map; import java.util.Set; import java.util.StringTokenizer; import java.util.regex.Matcher; import java.util.regex.Pattern; import org.eclipse.emf.codegen.ecore.genmodel.GenModelPackage; import org.eclipse.emf.codegen.util.CodeGenUtil; import org.eclipse.emf.common.util.BasicDiagnostic; import org.eclipse.emf.common.util.BasicEList; import org.eclipse.emf.common.util.Diagnostic; import org.eclipse.emf.common.util.EList; import org.eclipse.emf.common.util.UniqueEList; import org.eclipse.emf.ecore.EAnnotation; import org.eclipse.emf.ecore.EAttribute; import org.eclipse.emf.ecore.EClass; import org.eclipse.emf.ecore.EClassifier; import org.eclipse.emf.ecore.EDataType; import org.eclipse.emf.ecore.EEnum; import org.eclipse.emf.ecore.EEnumLiteral; import org.eclipse.emf.ecore.EGenericType; import org.eclipse.emf.ecore.EModelElement; import org.eclipse.emf.ecore.ENamedElement; import org.eclipse.emf.ecore.EObject; import org.eclipse.emf.ecore.EOperation; import org.eclipse.emf.ecore.EPackage; import org.eclipse.emf.ecore.EParameter; import org.eclipse.emf.ecore.EReference; import org.eclipse.emf.ecore.EStructuralFeature; import org.eclipse.emf.ecore.ETypeParameter; import org.eclipse.emf.ecore.ETypedElement; import org.eclipse.emf.ecore.EcoreFactory; import org.eclipse.emf.ecore.EcorePackage; import org.eclipse.emf.ecore.util.EcoreSwitch; import org.eclipse.emf.ecore.util.EcoreUtil; import org.eclipse.emf.ecore.util.ExtendedMetaData; import org.eclipse.emf.ecore.xmi.impl.EMOFExtendedMetaData; import com.sap.emf.importer.moin.rose.RoseImporterPlugin; import com.sap.emf.importer.moin.rose.parser.RoseNode; import com.sap.emf.importer.moin.rose.parser.Util; /** * Traverses the Rose file and create eCore object in memory. */ public class RoseEcoreBuilder implements RoseVisitor { private static final String SAP2MOF_OPERATION_CODE_OCL = "\"sap2mof.OperationCodeOcl\""; private static final String UML2MOF_CLUSTERED_IMPORT = "\"uml2mof.clusteredImport\""; private static final String ROSE2MOF_CONSTRAINED_ELEMENTS = "\"rose2mof.constrainedElements\""; private static final String ROSE2MOF_RETURN_MULTIPLICITY = "rose2mof.return.multiplicity"; private static final String MOF = "\"MOF\""; private static final String VALIDATION_DELEGATES = "validationDelegates"; private static final String INVOCATION_DELEGATES = "invocationDelegates"; private static final String INV = "inv"; private static final String COLON = ":"; private static final String DELEGATE_URI = "http://www.eclipse.org/emf/2002/Ecore/OCL"; private static final String ECORE_NS_URI = "http://www.eclipse.org/emf/2002/Ecore"; private static final String CONSTRAINTS = "constraints"; //do you want to parse the semantic tab info? public boolean activateSemanticsTab = false; class DeferredConstraintAnnotation{ public DeferredConstraintAnnotation(String constraintName, String constraintExpr, String clsName2) { name=constraintName; expr=constraintExpr; clsName= clsName2; } String name; String expr; String clsName; } public boolean noQualify = false; public boolean unsettablePrimitive = "true".equals(System.getProperty("EMF_UNSETTABLE_PRIMITIVE")); protected RoseUtil roseUtil; protected Set<EModelElement> bounded = new HashSet<EModelElement>(); protected Map<EStructuralFeature, String> eStructuralFeatureToXMLNamespaceMap = new HashMap<EStructuralFeature, String>(); protected List<EStructuralFeature> eStructuralFeatures = new BasicEList.FastCompare<EStructuralFeature>(); protected Map<EEnum, String> eEnums = new HashMap<EEnum, String>(); protected Map<String, Object> idToParentMap = new HashMap<String, Object>(); protected EReference ref1 = null; protected EReference ref2 = null; protected RoseNode role1 = null; protected RoseNode role2 = null; protected EGenericType eGenericType1; protected EGenericType eGenericType2; protected Set<EAttribute> attributesToConvert = new HashSet<EAttribute>(); // This could potentially map every created model element to its corresponding Rose node. // However, for now we're only using it as needed. // protected Map<EModelElement, RoseNode> eModelElementToRoseNodeMap = new HashMap<EModelElement, RoseNode>(); private final List<DeferredConstraintAnnotation> deferredConstraints = new ArrayList<RoseEcoreBuilder.DeferredConstraintAnnotation>(); private final List<EClassifier> allClasses = new ArrayList<EClassifier>(); public RoseEcoreBuilder(RoseUtil roseUtil) { super(); this.roseUtil = roseUtil; } @Override public void visitList(RoseNode roseNode) { // Nothing to do } @Override public void visitObject(RoseNode roseNode) { String roseNodeValue = roseNode.getValue(); String objectKey = roseNode.getKey(); String objectType = Util.getType(roseNodeValue); String objectName = Util.getName(roseNodeValue); // System.out.println("---> visitObject,,, objectKey - objectType - objectName: " + objKey + ", " + objType + ", " + objectName); // Get the parent object. // RoseNode currentNode = roseNode; Object parent = currentNode.getNode(); while (parent == null) { currentNode = currentNode.getParent(); parent = currentNode.getNode(); } visitObject(roseNode, roseNodeValue, objectKey, objectType, objectName, parent); } protected void visitObject(RoseNode roseNode, String roseNodeValue, String objectKey, String objectType, String objectName, Object parent) { if (objectKey.equals("") && objectType.equals(RoseStrings.CLASS_CATEGORY)) { visitClassCategory(roseNode, roseNodeValue, objectKey, objectName, parent); } else if (objectType.equals(RoseStrings.CLASS)) { if (RoseStrings.CONSTRAINT_STEREOTYPE.equals(roseNode.getStereotype())){ visitConstraintClass(roseNode, roseNodeValue, objectKey, objectName, parent); } else{ visitClass(roseNode, roseNodeValue, objectKey, objectName, parent); } } else if (objectType.equals(RoseStrings.OPERATION)) { visitOperation(roseNode, roseNodeValue, objectKey, objectName, parent); } else if (objectType.equals(RoseStrings.PARAMETER)) { visitParameter(roseNode, roseNodeValue, objectKey, objectName, parent); } else if (objectType.equals(RoseStrings.INHERITANCE_RELATIONSHIP)) { visitInheritanceRelationship(roseNode, roseNodeValue, objectKey, objectName, parent); } else if (objectType.equals(RoseStrings.CLASSATTRIBUTE) && (!roseNode.isDerived() || !"reference".equals(roseNode.getStereotype()))) { visitClassattribute(roseNode, roseNodeValue, objectKey, objectName, parent); } else if (objectType.equals(RoseStrings.ASSOCIATION)) { visitAssociation(roseNode, roseNodeValue, objectKey, objectName, parent); } else if (objectType.equals(RoseStrings.ROLE) && !objectName.startsWith("/")) { visitRole(roseNode, roseNodeValue, objectKey, objectName, parent); } } protected void visitClassCategory(RoseNode roseNode, String roseNodeValue, String objectKey, String objectName, Object parent) { // Map to an EPackage. // if (roseNode.isLoaded()) { String id = roseNode.getRoseId(); if (idToParentMap.containsKey(id)) { parent = idToParentMap.get(id); } EPackage ePackage = EcoreFactory.eINSTANCE.createEPackage(); addDelegateAnnotation(ePackage); if (parent instanceof EPackage) { // Add to package. // ((EPackage)parent).getESubpackages().add(ePackage); } else if (parent instanceof EList<?>) { @SuppressWarnings("unchecked") EList<Object> list = (EList<Object>)parent; list.add(ePackage); } // add clustered imports addPackagesFromClusteredImports(roseNode, ePackage, UML2MOF_CLUSTERED_IMPORT); setEPackageProperties(roseNode, ePackage, objectName.toLowerCase()); } else { idToParentMap.put(roseNode.getRoseId(), parent); } } /** * @param roseNode * @param ePackage * @param property */ private void addPackagesFromClusteredImports(RoseNode roseNode, EPackage ePackage, String property) { for(RoseNode n: roseNode.getNodes()){ if(RoseStrings.ATTRIBUTE_SET.equals(Util.getType(n.getValue()))){ for(RoseNode attr: n.getNodes()){ if(RoseStrings.ATTRIBUTE.equals(Util.getType(attr.getValue()))){ String[] pkgNames = parseAttributesFromNode(attr, property); if(pkgNames == null) { continue; } for(String pkgName: pkgNames){ EPackage pkg = EcoreFactory.eINSTANCE.createEPackage(); ePackage.getESubpackages().add(pkg); setEPackageProperties(roseNode, pkg, pkgName); } } } } } } protected void visitConstraintClass(RoseNode constraintClassRoseNode, String roseNodeValue, String objectKey, String objectName, Object parent) { Util.getName(roseNodeValue); String constraintName=objectName; String constraintExpr=""; for(RoseNode n:constraintClassRoseNode.getNodes()){ if(RoseStrings.OPERATIONS.equalsIgnoreCase(Util.getType(n.getValue()))){ for(RoseNode op: n.getNodes()){ if(RoseStrings.OPERATION.equals(Util.getType(op.getValue())) && RoseStrings.OCL_OPERATION.equals(Util.getName(op.getValue()))){ String fullOCLStatement = op.getSemantics(); int invStart= fullOCLStatement.indexOf(INV); if(invStart!=-1){ int colonStart=fullOCLStatement.indexOf(COLON); String newConstraintName=fullOCLStatement.substring(invStart+INV.length(),colonStart).trim(); if(!newConstraintName.isEmpty()) { constraintName=newConstraintName; } constraintExpr= fullOCLStatement.substring(colonStart+1).trim(); }else{ constraintExpr= fullOCLStatement; } } } } } if(!(parent instanceof EClassifier)){ if(parent instanceof EPackage){ for(RoseNode n: constraintClassRoseNode.getNodes()){ if(RoseStrings.ATTRIBUTE_SET.equals(Util.getType(n.getValue()))){ for(RoseNode attr: n.getNodes()){ if(RoseStrings.ATTRIBUTE.equals(Util.getType(attr.getValue()))){ String[] clsNames = parseAttributesFromNode(attr, ROSE2MOF_CONSTRAINED_ELEMENTS); if(clsNames == null) { continue; } for(String clsName: clsNames){ deferredConstraints.add(new DeferredConstraintAnnotation(constraintName, constraintExpr, clsName)); } } } } } } return; } EClassifier clazz = (EClassifier) parent; addConstraintToNamedElement(constraintName, constraintExpr, clazz); } private String[] parseAttributesFromNode(RoseNode node, String property){ // there should be exactly 3 columns if(node.getNodes().size()!=3) return null; // first column MOF String firstAttrValue= node.getNodes().get(0).getValue(); if(!MOF.equals(firstAttrValue)) return null; //second column should define the given property" String secondAttrValue= node.getNodes().get(1).getValue(); if(!property.equals(secondAttrValue)) return null; String thirdAttrValue= Util.getName(node.getNodes().get(2).getNodes().get(0).getValue()); // we have found a constraint if(thirdAttrValue == null && SAP2MOF_OPERATION_CODE_OCL.equals(property)){ List<RoseNode> nodes = node.getNodes().get(2).getNodes().get(0).getNodes(); String[] forthAttrValue = new String[nodes.size()]; int i = 0; for(RoseNode n: nodes){ forthAttrValue[i] = n.getValue(); i++; } return forthAttrValue; } return thirdAttrValue.split(","); } public void processDefferendConstraints(){ for(EClassifier cls: allClasses){ for(DeferredConstraintAnnotation anno: deferredConstraints){ if(cls.getName().equals(anno.clsName)){ addConstraintToNamedElement(anno.name, anno.expr, cls); } } } } /** * @param constraintName * @param constraintExpr * @param element */ private void addConstraintToNamedElement(String constraintName, String constraintExpr, ENamedElement element) { EcoreUtil.setAnnotation(element, DELEGATE_URI, constraintName, constraintExpr); String csString=EcoreUtil.getAnnotation(element, ECORE_NS_URI, CONSTRAINTS); if(csString==null) { EcoreUtil.setAnnotation(element, ECORE_NS_URI, CONSTRAINTS, constraintName); } else { EcoreUtil.setAnnotation(element, ECORE_NS_URI, CONSTRAINTS, csString+" "+constraintName); } } protected void visitClass(RoseNode roseNode, String roseNodeValue, String objectKey, String objectName, Object parent) { if (objectName == null || objectName.length() == 0) { String quid = roseNode.getRoseId(); if (quid != null) { quid = quid.substring(1, quid.length() - 1); } objectName = "Unnamed" + quid; error(RoseImporterPlugin.INSTANCE.getString("_UI_UnnamedClass_message", new Object []{ objectName })); } // Map to EClass, EEnum or EInerface. // Note that we do not map structure and primitive type class. // RoseNode stereoTypeNode = roseNode.findNodeWithKey(RoseStrings.STEREOTYPE); if (stereoTypeNode != null) { String stereoTypeValue = stereoTypeNode.getValue(); stereoTypeValue = stereoTypeValue.substring(1, stereoTypeValue.length() - 1); if (stereoTypeValue.equals(RoseStrings.INTERFACE)) { // Map to an EClass. // EClass eClass = EcoreFactory.eINSTANCE.createEClass(); allClasses.add(eClass); String classifierName = roseNode.getClassifierName(); if (classifierName == null || classifierName.length() == 0) { classifierName = validName(upperCaseName(objectName)); } eClass.setName(classifierName); roseNode.setNode(eClass); setEClassProperties(roseNode, eClass); eClass.setInterface(true); eClass.setAbstract(true); build(roseNode, parent, eClass); } else if (stereoTypeValue.equalsIgnoreCase(RoseStrings.ENUMERATION)) { // Map to an EEnum. EEnum eEnum = EcoreFactory.eINSTANCE.createEEnum(); String classifierName = roseNode.getClassifierName(); if (classifierName == null || classifierName.length() == 0) { classifierName = validName(upperCaseName(objectName)); } eEnum.setName(classifierName); roseNode.setNode(eEnum); setEEnumProperties(roseNode, eEnum); build(roseNode, parent, eEnum); } else if (stereoTypeValue.equalsIgnoreCase("datatype") || stereoTypeValue.equalsIgnoreCase("primitive")) { // Map to an EDataType. // EDataType eDataType = EcoreFactory.eINSTANCE.createEDataType(); String classifierName = roseNode.getClassifierName(); if (classifierName == null || classifierName.length() == 0) { classifierName = validName(upperCaseName(objectName)); } eDataType.setName(classifierName); roseNode.setNode(eDataType); setEDataTypeProperties(roseNode, eDataType); build(roseNode, parent, eDataType); String uml2MOFCorbaType = roseNode.getUML2MOFCorbaType(); if (uml2MOFCorbaType != null) { uml2MOFCorbaType = uml2MOFCorbaType.trim(); int start = uml2MOFCorbaType.indexOf("typedef "); if (start != -1) { uml2MOFCorbaType = uml2MOFCorbaType.substring(8); int end = uml2MOFCorbaType.lastIndexOf(" "); if (end != -1) { uml2MOFCorbaType = uml2MOFCorbaType.substring(0, end); } } if (uml2MOFCorbaType != null && uml2MOFCorbaType.length() != 0) { roseUtil.typeTable.put(eDataType, uml2MOFCorbaType); } } } else if (stereoTypeValue.equalsIgnoreCase("javatype")) { // Map to an EDataType. // EDataType eDataType = EcoreFactory.eINSTANCE.createEDataType(); String classifierName = roseNode.getClassifierName(); if (classifierName == null || classifierName.length() == 0) { int index = objectName.lastIndexOf("."); classifierName = validName(upperCaseName(index == -1 ? objectName : objectName.substring(index + 1))); } int index = objectName.lastIndexOf("."); eDataType.setName(validName(upperCaseName(index == -1 ? objectName : objectName.substring(index + 1)))); eDataType.setInstanceClassName(objectName); roseNode.setNode(eDataType); setEDataTypeProperties(roseNode, eDataType); build(roseNode, parent, eDataType); } else if (stereoTypeValue.equalsIgnoreCase("abstract")) { // Map to an EClass. // EClass eClass = EcoreFactory.eINSTANCE.createEClass(); allClasses.add(eClass); String classifierName = roseNode.getClassifierName(); if (classifierName == null || classifierName.length() == 0) { classifierName = validName(upperCaseName(objectName)); } eClass.setName(classifierName); roseNode.setNode(eClass); setEClassProperties(roseNode, eClass); build(roseNode, parent, eClass); } else if (stereoTypeValue.equalsIgnoreCase("MapEntry")) { // Map to an EClass. // EClass eClass = EcoreFactory.eINSTANCE.createEClass(); allClasses.add(eClass); String classifierName = roseNode.getClassifierName(); if (classifierName == null || classifierName.length() == 0) { classifierName = validName(upperCaseName(objectName)); } eClass.setName(classifierName); roseNode.setNode(eClass); setEClassProperties(roseNode, eClass); eClass.setInstanceClassName("java.util.Map$Entry"); build(roseNode, parent, eClass); } else if (stereoTypeValue.equalsIgnoreCase("constraint")) { // look for an "OCL" operation and if found, extract OCL expression from Semantics node // first, find owning class String x=objectName; x = x+""; } else { warning(RoseImporterPlugin.INSTANCE.getString("_UI_UnrecognizedStereotype_message", new Object []{ stereoTypeValue, objectName })); // Map to an eClass. // EClass eClass = EcoreFactory.eINSTANCE.createEClass(); allClasses.add(eClass); String classifierName = roseNode.getClassifierName(); if (classifierName == null || classifierName.length() == 0) { classifierName = validName(upperCaseName(objectName)); } eClass.setName(classifierName); roseNode.setNode(eClass); setEClassProperties(roseNode, eClass); build(roseNode, parent, eClass); } } else { // Map to an eClass. // EClass eClass = EcoreFactory.eINSTANCE.createEClass(); allClasses.add(eClass); String classifierName = roseNode.getClassifierName(); if (classifierName == null || classifierName.length() == 0) { classifierName = validName(upperCaseName(objectName)); } eClass.setName(classifierName); roseNode.setNode(eClass); setEClassProperties(roseNode, eClass); build(roseNode, parent, eClass); } } protected void visitOperation(RoseNode roseNode, String roseNodeValue, String objectKey, String objectName, Object parent) { // Map to an EOperation. if (RoseStrings.OCL_OPERATION.equals(objectName)) return; EOperation eOperation = EcoreFactory.eINSTANCE.createEOperation(); String operationName = roseNode.getOperationName(); addConstraintsForOperation(roseNode, eOperation); String rawName = operationName; if (operationName == null || operationName.length() == 0) { rawName = objectName; operationName = validName(objectName); } int index = rawName.lastIndexOf(">"); if (index != -1) { if (rawName.startsWith("<")) { String templateParameters = rawName.substring(1, index); eOperation.getETypeParameters().addAll(parseTemplateParameters(templateParameters)); } operationName = rawName.substring(index + 1).trim(); if (roseNode.getOperationName() == null || roseNode.getOperationName().length() == 0) { operationName = validName(operationName); } } eOperation.setName(operationName); roseNode.setNode(eOperation); setResultType(roseNode, eOperation); setEOperationProperties(roseNode, eOperation); if (parent instanceof EClass) { // Add to an EClass // ((EClass)parent).getEOperations().add(eOperation); } } /** * @param roseNode the node, containing the rose operation * @param eOperation the operation the constraint should be added to */ private void addConstraintsForOperation(RoseNode roseNode, EOperation eOperation) { for(RoseNode n: roseNode.getNodes()){ if(RoseStrings.ATTRIBUTE_SET.equals(Util.getType(n.getValue()))){ for(RoseNode attr: n.getNodes()){ if(RoseStrings.ATTRIBUTE.equals(Util.getType(attr.getValue()))){ String[] constraints = parseAttributesFromNode(attr, SAP2MOF_OPERATION_CODE_OCL); if(constraints == null) { continue; } StringBuilder result = new StringBuilder(); for(String clsName: constraints){ result.append(clsName); result.append('\n'); } result.delete(result.length()-1, result.length()); // delete last \n again String expr = result.substring(result.indexOf("body:") + 5).trim(); //TODO ensure that the constrained name is always body and not pre/post/... addConstraintToNamedElement("body", expr, eOperation); } } } } } protected void visitParameter(RoseNode roseNode, String roseNodeValue, String objectKey, String objectName, Object parent) { // Map to an EParameter as input parameter for operation. // EParameter eParameter = EcoreFactory.eINSTANCE.createEParameter(); eParameter.setName(validName(objectName)); roseNode.setNode(eParameter); // Do this first for better error message during setEParameterProperties. // if (parent instanceof EOperation) { ((EOperation)parent).getEParameters().add(eParameter); } setEParameterProperties(roseNode, eParameter); } protected void visitInheritanceRelationship(RoseNode roseNode, String roseNodeValue, String objectKey, String objectName, Object parent) { String quidu = roseNode.getRoseRefId(); if (quidu != null && !quidu.equals("")) { quidu = quidu.substring(1, quidu.length() - 1); } List<String> superList = roseUtil.superTable.get(parent); if (superList == null) { superList = new ArrayList<String>(); roseUtil.superTable.put(parent, superList); } superList.add(quidu); superList.add(roseNode.getStereotype()); } protected void visitClassattribute(RoseNode roseNode, String roseNodeValue, String objectKey, String objectName, Object parent) { // Map to EAttribute, or EEnumLiteral. // if (parent instanceof EEnum) { EEnumLiteral eEnumLiteral = ((EEnum)parent).getEEnumLiteral(objectName); if (eEnumLiteral == null) { eEnumLiteral = EcoreFactory.eINSTANCE.createEEnumLiteral(); String literalName = roseNode.getAttributeName(); if (literalName == null || literalName.length() == 0) { literalName = validName(objectName); } else { eEnumLiteral.setLiteral(objectName); } eEnumLiteral.setName(literalName); roseNode.setNode(eEnumLiteral); if (!setEEnumLiteralProperties(roseNode, eEnumLiteral)) { if (((EEnum)parent).getELiterals() == null) { eEnumLiteral.setValue(0); } else { eEnumLiteral.setValue(((EEnum)parent).getELiterals().size()); } } ((EEnum)parent).getELiterals().add(eEnumLiteral); } } else if (parent instanceof EClassifier) { String stereoTypeValue = null; RoseNode stereoTypeNode = roseNode.findNodeWithKey(RoseStrings.STEREOTYPE); if (stereoTypeNode != null) { stereoTypeValue = stereoTypeNode.getValue(); stereoTypeValue = stereoTypeValue.substring(1, stereoTypeValue.length() - 1); } if ((parent instanceof EDataType || parent instanceof EClass) && "javaclass".equalsIgnoreCase(stereoTypeValue)) { roseUtil.typeTable.remove(parent); ((EClassifier)parent).setInstanceTypeName(objectName); } else if ((parent instanceof EDataType || parent instanceof EClass) && "parameter".equalsIgnoreCase(stereoTypeValue)) { String attributeName = roseNode.getAttributeName(); if (attributeName == null || attributeName.length() == 0) { attributeName = objectName; } ETypeParameter eTypeParameter = parseTemplateParameter(attributeName); roseNode.setNode(eTypeParameter); ((EClassifier)parent).getETypeParameters().add(eTypeParameter); } else if (parent instanceof EClass) { EAttribute eAttribute = EcoreFactory.eINSTANCE.createEAttribute(); String attributeName = roseNode.getAttributeName(); if (attributeName == null || attributeName.length() == 0) { attributeName = validName(objectName); } eAttribute.setName(attributeName); roseNode.setNode(eAttribute); ((EClass)parent).getEStructuralFeatures().add(eAttribute); setEAttributeProperties(roseNode, eAttribute); if (eAttribute.getUpperBound() == 0) { eAttribute.setUpperBound(1); } // We will need to check the containment if we have to convert the EAttribute to an EReference later. // if (roseNode.getContainment() != null) { eModelElementToRoseNodeMap.put(eAttribute, roseNode); } // Convert to an EReference. // if ("reference".equals(stereoTypeValue)) { attributesToConvert.add(eAttribute); } } } } protected void visitAssociation(RoseNode roseNode, String roseNodeValue, String objectKey, String objectName, Object parent) { ref1 = null; ref2 = null; role1 = null; role2 = null; } protected void visitRole(RoseNode roseNode, String roseNodeValue, String objectKey, String objectName, Object parent) { // map to EReference when is navigable // EReference ref = EcoreFactory.eINSTANCE.createEReference(); ref.setUpperBound(0); String referenceName = roseNode.getReferenceName(); String rawName = referenceName; if (referenceName == null || referenceName.length() == 0) { rawName = objectName; referenceName = validName(objectName); } EGenericType eGenericType = null; int index = rawName.indexOf("<"); if (index != -1) { eGenericType = EcoreFactory.eINSTANCE.createEGenericType(); if (rawName.endsWith(">")) { String templateArguments = rawName.substring(index + 1, rawName.length() - 1); eGenericType.getETypeArguments().addAll(parseTemplateArguments(templateArguments)); } ref.setEGenericType(eGenericType); referenceName = rawName.substring(0, index); if (roseNode.getReferenceName() == null || roseNode.getReferenceName().length() == 0) { referenceName = validName(referenceName); } } ref.setName(referenceName); roseNode.setNode(ref); setEReferenceProperties(roseNode, ref); if (ref1 == null) { ref1 = ref; eGenericType1 = eGenericType; } else if (ref2 == null) { ref2 = ref; eGenericType2 = eGenericType; } if (role1 == null) { role1 = roseNode; } else if (role2 == null) { role2 = roseNode; } if (ref1 != null && ref2 != null && role1 != null && role2 != null) { String ref1Quidu = role1.getRoseRefId(); if (ref1Quidu != null && !ref1Quidu.equals("")) { ref1Quidu = ref1Quidu.substring(1, ref1Quidu.length() - 1); } String ref2Quidu = role2.getRoseRefId(); if (ref2Quidu != null && !ref2Quidu.equals("")) { ref2Quidu = ref2Quidu.substring(1, ref2Quidu.length() - 1); } //boolean ref1Navigable = role1.isNavigable(); //boolean ref2Navigable = role2.isNavigable(); boolean ref1Navigable; boolean ref2Navigable; ref2Navigable = role1.getSap2MofStore(); ref1Navigable = role2.getSap2MofStore(); if (ref1Navigable) { ref2.setEOpposite(ref1); setEReferenceIsContainment(ref1, role1, role2); roseUtil.refTable.put(ref1, ref2Quidu); TableObject obj = (TableObject)roseUtil.quidTable.get(ref1Quidu); if (obj != null) { roseUtil.typeTable.put(eGenericType1 == null ? ref1 : eGenericType1, obj.getName()); } else { warning(RoseImporterPlugin.INSTANCE.getString("_UI_UnresolvedTypeNameFor_message", new Object []{ role1.getRoseSupplier(), ref1.getName() })); roseUtil.typeTable.put(eGenericType1 == null ? ref1 : eGenericType1, "EObject"); } } else { if (ref1.getName() != null && ref1.getName().length() > 0) { EAnnotation oppositeRoleNameAnnotation = ref2.getEAnnotation(EMOFExtendedMetaData.EMOF_PACKAGE_NS_URI_2_0); if (oppositeRoleNameAnnotation == null) { oppositeRoleNameAnnotation = EcoreFactory.eINSTANCE.createEAnnotation(); oppositeRoleNameAnnotation.setSource(EMOFExtendedMetaData.EMOF_PACKAGE_NS_URI_2_0); ref2.getEAnnotations().add(oppositeRoleNameAnnotation); } else { oppositeRoleNameAnnotation.getDetails().clear(); } oppositeRoleNameAnnotation.getDetails().put("Property.oppositeRoleName", ref1.getName()); } } if (ref2Navigable) { ref1.setEOpposite(ref2); setEReferenceIsContainment(ref2, role2, role1); roseUtil.refTable.put(ref2, ref1Quidu); TableObject obj = (TableObject)roseUtil.quidTable.get(ref2Quidu); if (obj != null) { roseUtil.typeTable.put(eGenericType2 == null ? ref2 : eGenericType2, obj.getName()); } else { warning(RoseImporterPlugin.INSTANCE.getString("_UI_UnresolvedTypeNameFor_message", new Object []{ role2.getRoseSupplier(), ref2.getName() })); roseUtil.typeTable.put(eGenericType2 == null ? ref2 : eGenericType2, "EObject"); } } else { if (ref2.getName() != null && ref2.getName().length() > 0) { EAnnotation oppositeRoleNameAnnotation = ref1.getEAnnotation(EMOFExtendedMetaData.EMOF_PACKAGE_NS_URI_2_0); if (oppositeRoleNameAnnotation == null) { oppositeRoleNameAnnotation = EcoreFactory.eINSTANCE.createEAnnotation(); oppositeRoleNameAnnotation.setSource(EMOFExtendedMetaData.EMOF_PACKAGE_NS_URI_2_0); ref1.getEAnnotations().add(oppositeRoleNameAnnotation); } else { oppositeRoleNameAnnotation.getDetails().clear(); } oppositeRoleNameAnnotation.getDetails().put("Property.oppositeRoleName", ref2.getName()); } } } if (ref.getUpperBound() == 0) { setEReferenceDefaultMultiplicity(ref); } } protected EList<EObject> getExtentFromTableObject(RoseNode roseNode) { String quid = roseNode.getRoseId(); if (quid != null) { quid = quid.substring(1, quid.length() - 1); } TableObject obj = (TableObject)roseUtil.quidTable.get(quid); return obj == null ? null : obj.getContainer().getExtent(); } protected void setEReferenceIsContainment(EReference ref, RoseNode role1, RoseNode role2) { boolean isAggregate = role2.isAggregate(); String containmentV = role1.getContainment(); if (isAggregate && (containmentV != null && containmentV.equalsIgnoreCase("by value"))) { EReference opposite = ref.getEOpposite(); if (opposite != null) { if (opposite.getUpperBound() != 1) { if (bounded.contains(opposite)) { error(RoseImporterPlugin.INSTANCE.getString("_UI_ContainerRelationUpperBound_message", new Object []{ ref.getName(), ref.getEOpposite().getName() })); } opposite.setUpperBound(1); } } ref.setContainment(true); } } protected void setResultType(RoseNode roseNode, EOperation eOperation) { /* String name = roseNode.getResult(); for (ETypeParameter eTypeParameter : eOperation.getETypeParameters()) { if (eTypeParameter.getName().equals(name)) { EGenericType eGenericType = EcoreFactory.eINSTANCE.createEGenericType(); eGenericType.setETypeParameter(eTypeParameter); eOperation.setEGenericType(eGenericType); return; } } */ String quid = roseNode.getRoseRefId(); if (quid != null && !quid.equals("")) { quid = quid.substring(1, quid.length() - 1); TableObject tableObj = (TableObject)roseUtil.quidTable.get(quid); if (tableObj != null) { roseUtil.typeTable.put(eOperation, tableObj.getName()); } else { warning(RoseImporterPlugin.INSTANCE.getString("_UI_UnresolvedTypeIDFor_message", new Object []{ quid, eOperation.getName() })); roseUtil.typeTable.put(eOperation, "EString"); } } else { String resultValue = getQualifiedTypeName(eOperation, roseNode.getResult()); if (resultValue != null && !resultValue.equalsIgnoreCase("void")) { if (!resultValue.equals("")) { eOperation.setEGenericType(parseTemplateArgument(resultValue)); } else { warning(RoseImporterPlugin.INSTANCE.getString("_UI_UnresolvedTypeNameFor_message", new Object []{ roseNode.getRoseSupplier(), eOperation.getName() })); roseUtil.typeTable.put(eOperation, "EString"); } } } } protected static final Pattern ANNOTATION_PATTERN = Pattern.compile("\\G\\s*((?>\\\\.|\\S)+)((?:\\s+(?>\\\\.|\\S)+\\s*+=\\s*(['\"])((?>\\\\.|.)*?)\\3)*)"); protected static final Pattern ANNOTATION_DETAIL_PATTERN = Pattern.compile("\\s+((?>\\\\.|\\S)+)\\s*+=\\s*((['\"])((?>\\\\.|.)*?)\\3)"); protected void setEModelElementProperties(RoseNode roseNode, EModelElement eModelElement) { String annotation = roseNode.getAnnotation(); if (annotation != null) { for (Matcher matcher = ANNOTATION_PATTERN.matcher(annotation); matcher.find();) { EAnnotation eAnnotation = EcoreFactory.eINSTANCE.createEAnnotation(); eAnnotation.setSource(CodeGenUtil.parseString(matcher.group(1))); for (Matcher detailMatcher = ANNOTATION_DETAIL_PATTERN.matcher(matcher.group(2)); detailMatcher.find();) { eAnnotation.getDetails().put(CodeGenUtil.parseString(detailMatcher.group(1)), CodeGenUtil.parseString(detailMatcher.group(4))); } eModelElement.getEAnnotations().add(eAnnotation); } } String documentation = roseNode.getDocumentation(); if (documentation != null) { EcoreUtil.setDocumentation(eModelElement, documentation); } String constraints = roseNode.getEcoreConstraints(); if (constraints != null) { List<String> constraintList = new ArrayList<String>(); for (StringTokenizer stringTokenizer = new StringTokenizer(constraints); stringTokenizer.hasMoreTokens();) { String constraint = stringTokenizer.nextToken(); constraintList.add(constraint); } EcoreUtil.setConstraints(eModelElement, constraintList); } } protected void setEPackageProperties(RoseNode roseNode, EPackage ePackage, String tentativeName) { roseNode.setNode(ePackage); setEModelElementProperties(roseNode, ePackage); String packageName = roseNode.getPackageName(); if (packageName == null || packageName.length() == 0) { packageName = validName(tentativeName); } ePackage.setName(packageName); String basePackage = roseNode.getBasePackage(); String prefix = validName(upperCaseName(roseNode.getPrefix())); String nsPrefix = roseNode.getNsPrefix() == null || roseNode.getNsPrefix().length() == 0 ? (String)roseUtil.packageNameToNSNameMap.get(packageName) : roseNode.getNsPrefix(); if (nsPrefix == null || nsPrefix.length() == 0) { nsPrefix = packageName; EPackage eSuperPackage = ePackage.getESuperPackage(); if (eSuperPackage != null) { nsPrefix = eSuperPackage.getNsPrefix() + "." + nsPrefix; } else if (basePackage != null && basePackage.length() != 0) { nsPrefix = basePackage + "." + nsPrefix; } } ePackage.setNsPrefix(nsPrefix); String nsURI = roseNode.getNsURI() == null || roseNode.getNsURI().length() == 0 ? (String)roseUtil.packageNameToNSURIMap.get(packageName) : roseNode.getNsURI(); if (nsURI == null || nsURI.length() == 0) { if (noQualify) { nsURI = nsPrefix + ".ecore"; } else { nsURI = "http:///" + nsPrefix.replace('.', '/') + ".ecore"; } } ePackage.setNsURI(nsURI); if (prefix != null && prefix.length() == 0) { prefix = null; } if (basePackage != null && basePackage.length() == 0) { basePackage = null; } if (prefix != null || basePackage != null) { List<String> information = new ArrayList<String>(); information.add(basePackage); information.add(prefix); roseUtil.getEPackageToInformationMap().put(ePackage, information); } } protected void setEClassProperties(RoseNode roseNode, EClass eClass) { setEModelElementProperties(roseNode, eClass); String xmlName = roseNode.getXMLName(); if (xmlName != null && xmlName.length() != 0) { ExtendedMetaData.INSTANCE.setName(eClass, xmlName); } int xmlContentKind = roseNode.getXMLContentKind(); if (xmlContentKind != 0) { ExtendedMetaData.INSTANCE.setContentKind(eClass, xmlContentKind); } eClass.setAbstract(roseNode.isAbstract()); } protected void setEDataTypeProperties(RoseNode roseNode, EDataType eDataType) { setEModelElementProperties(roseNode, eDataType); String xmlName = roseNode.getXMLName(); if (xmlName != null && xmlName.length() != 0) { ExtendedMetaData.INSTANCE.setName(eDataType, xmlName); } eDataType.setSerializable(!roseNode.isAbstract()); } protected void setEEnumProperties(RoseNode roseNode, EEnum eEnum) { setEModelElementProperties(roseNode, eEnum); String xmlName = roseNode.getXMLName(); if (xmlName != null && xmlName.length() != 0) { ExtendedMetaData.INSTANCE.setName(eEnum, xmlName); } String value = roseNode.getDocumentation(); if (value != null && !value.equals("")) { eEnums.put(eEnum, value); } } protected void populateEEnumFromDocumentation(EEnum eEnum, String documentation) { // process documentation info and create eEnumLiteral for each line // List<EEnumLiteral> eLiterals = eEnum.getELiterals(); for (StringTokenizer stringTokenizer = new StringTokenizer(documentation, ", \n\r\t"); stringTokenizer.hasMoreTokens();) { String literalV = stringTokenizer.nextToken(); String name = literalV; String number = ""; int ind = literalV.indexOf("="); if (ind != -1) { name = literalV.substring(0, ind); number = literalV.substring(ind + 1, literalV.length()); } int numberValue = 0; if (!number.equals("")) { numberValue = Integer.parseInt(number); } else if (!eLiterals.isEmpty()) { numberValue = eLiterals.get(eLiterals.size() - 1).getValue() + 1; } if (!name.equals("")) { EEnumLiteral lit = eEnum.getEEnumLiteral(name); if (lit == null) { lit = EcoreFactory.eINSTANCE.createEEnumLiteral(); lit.setName(validName(name)); lit.setValue(numberValue); eLiterals.add(lit); } else { lit.setValue(numberValue); } } } } protected void setEOperationProperties(RoseNode roseNode, EOperation eOperation) { setETypedElementProperties(roseNode, eOperation); eOperation.setOrdered(roseNode.isOrdered(true)); eOperation.setUnique(roseNode.isUnique(true)); String semantics = roseNode.getSemantics(); if (semantics != null && activateSemanticsTab) { EAnnotation eAnnotation = eOperation.getEAnnotation(GenModelPackage.eNS_URI); if (eAnnotation == null) { eAnnotation = EcoreFactory.eINSTANCE.createEAnnotation(); eAnnotation.setSource(GenModelPackage.eNS_URI); eOperation.getEAnnotations().add(eAnnotation); } eAnnotation.getDetails().put("body", semantics); } String exceptions = roseNode.getExceptions(); if (exceptions != null) { for (StringTokenizer stringTokenizer = new StringTokenizer(exceptions.trim(), ","); stringTokenizer.hasMoreTokens();) { // This handles Rose 2003 format, e.g., // Logical View::JavaException[40722F9D0294] // String exception = stringTokenizer.nextToken().trim(); if (exception.indexOf("[") != -1) { exception = exception.substring(0, exception.indexOf("[")); } if (exception != null && !exception.equals("")) { EGenericType eGenericType = parseTemplateArgument(exception); eOperation.getEGenericExceptions().add(eGenericType); } /* String exceptionValue = getQualifiedTypeName(eOperation, exception); if (exceptionValue != null && !exceptionValue.equals("")) { EAnnotation eAnnotation = EcoreFactory.eINSTANCE.createEAnnotation(); eAnnotation.getReferences().add(eOperation); eAnnotation.getDetails().put("position", Integer.toString(count++)); roseUtil.typeTable.put(eAnnotation, exceptionValue); } */ else { warning(RoseImporterPlugin.INSTANCE.getString("_UI_UnresolvedTypeNameFor_message", new Object []{ roseNode.getRoseSupplier(), eOperation.getName() })); } } } String stereotype = roseNode.getStereotype(); if (stereotype != null) { if ("inv".equals(stereotype)) { eOperation.setEType(EcorePackage.Literals.EBOOLEAN); eOperation.getEParameters().clear(); EParameter eParameter = EcoreFactory.eINSTANCE.createEParameter(); eParameter.setName("diagnostics"); eParameter.setEType(EcorePackage.Literals.EDIAGNOSTIC_CHAIN); eOperation.getEParameters().add(eParameter); eParameter = EcoreFactory.eINSTANCE.createEParameter(); eParameter.setName("context"); EGenericType eGenericType = EcoreFactory.eINSTANCE.createEGenericType(); eGenericType.setEClassifier(EcorePackage.Literals.EMAP); EGenericType eGenericKeyType = EcoreFactory.eINSTANCE.createEGenericType(); eGenericKeyType.setEClassifier(EcorePackage.Literals.EJAVA_OBJECT); eGenericType.getETypeArguments().add(eGenericKeyType); EGenericType eGenericValueType = EcoreFactory.eINSTANCE.createEGenericType(); eGenericValueType.setEClassifier(EcorePackage.Literals.EJAVA_OBJECT); eGenericType.getETypeArguments().add(eGenericValueType); eParameter.setEGenericType(eGenericType); eOperation.getEParameters().add(eParameter); } } } protected void setEAttributeProperties(RoseNode roseNode, EAttribute eAttribute) { eStructuralFeatures.add(eAttribute); String quid = roseNode.getRoseRefId(); if (quid != null && !quid.equals("")) { quid = quid.substring(1, quid.length() - 1); TableObject tableObj = (TableObject)roseUtil.quidTable.get(quid); if (tableObj != null) { roseUtil.typeTable.put(eAttribute, tableObj.getName()); } else { warning(RoseImporterPlugin.INSTANCE.getString("_UI_UnresolvedTypeIDFor_message", new Object []{ quid, eAttribute.getName() })); roseUtil.typeTable.put(eAttribute, "String"); } } else { String roseType = roseNode.getType(); if (roseType == null || roseType.equals("")) { roseUtil.typeTable.put(eAttribute, "String"); warning(RoseImporterPlugin.INSTANCE.getString("_UI_AttributeDoesNotDefineItsType_message", new Object []{ eAttribute.getName() })); } else { eAttribute.setEGenericType(parseTemplateArgument(roseType)); } } // default value // String initv = roseNode.getInitV(); if (initv != null && initv.length() >= 2) { if (initv.charAt(0) == '\'' && initv.charAt(initv.length() - 1) == '\'') { try { int i = CodeGenUtil.parseChar(initv.substring(1, initv.length() - 1)); initv = Integer.toString(i); } catch (IllegalArgumentException e) { error(RoseImporterPlugin.INSTANCE.getString("_UI_InvalidDefaultValueForAttribute_message", new Object []{ eAttribute.getName() })); initv = null; } } else if (initv.charAt(0) == '\"' && initv.charAt(initv.length() - 1) == '\"') { try { initv = CodeGenUtil.parseString(initv.substring(1, initv.length() - 1)); } catch (IllegalArgumentException e) { error(RoseImporterPlugin.INSTANCE.getString("_UI_InvalidDefaultValueForAttribute_message", new Object []{ eAttribute.getName() })); initv = null; } } } if (initv != null) { eAttribute.setDefaultValueLiteral(initv); } setEStructuralFeatureProperties(roseNode, eAttribute); eAttribute.setDerived(roseNode.isDerived()); eAttribute.setTransient(roseNode.isTransient()); eAttribute.setVolatile(roseNode.isVolatile()); eAttribute.setChangeable(roseNode.isChangeable()); eAttribute.setOrdered(roseNode.isOrdered(true)); eAttribute.setUnique(roseNode.isUnique(true)); eAttribute.setUnsettable(roseNode.isUnsettable()); eAttribute.setID(roseNode.isID()); setEStructuralFeatureVisibility(roseNode, eAttribute); } protected void setEReferenceProperties(RoseNode roseNode, EReference eReference) { eStructuralFeatures.add(eReference); eReference.setDerived(roseNode.getParent().getParent().isDerived()); setEStructuralFeatureProperties(roseNode, eReference); // eReference.setNavigable(roseNode.isNavigable()); eReference.setTransient(roseNode.isTransient()); eReference.setVolatile(roseNode.isVolatile()); eReference.setChangeable(roseNode.isChangeable()); eReference.setResolveProxies(roseNode.isResolveProxies()); eReference.setUnsettable(roseNode.isUnsettable()); eReference.setOrdered(roseNode.isOrdered(true)); eReference.setUnique(roseNode.isUnique(true)); setEStructuralFeatureVisibility(roseNode, eReference); } protected void setEStructuralFeatureProperties(RoseNode roseNode, EStructuralFeature eStructuralFeature) { setETypedElementProperties(roseNode, eStructuralFeature); String xmlName = roseNode.getXMLName(); if (xmlName != null && xmlName.length() != 0) { ExtendedMetaData.INSTANCE.setName(eStructuralFeature, xmlName); } int xmlFeatureKind = roseNode.getXMLFeatureKind(); if (xmlFeatureKind != 0) { ExtendedMetaData.INSTANCE.setFeatureKind(eStructuralFeature, xmlFeatureKind); } String xmlNamespace = roseNode.getXMLNamespace(); if (xmlNamespace != null && xmlNamespace.length() != 0) { eStructuralFeatureToXMLNamespaceMap.put(eStructuralFeature, xmlNamespace); } } protected void setETypedElementProperties(RoseNode roseNode, ETypedElement eTypedElement) { setEModelElementProperties(roseNode, eTypedElement); String multiplicity; if ( eTypedElement instanceof EReference) { multiplicity = roseNode.getRoleMultiplicity(); } else if (eTypedElement instanceof EOperation) { multiplicity = roseNode.getAttributeValue("MOF", ROSE2MOF_RETURN_MULTIPLICITY); if (multiplicity == null) { multiplicity = roseNode.getStereotype(); // default } } else if (eTypedElement instanceof EParameter) { multiplicity = roseNode.getAttributeValue("MOF", "uml2mof.multiplicity"); if (multiplicity == null) { multiplicity = roseNode.getStereotype(); // default } } else if (eTypedElement instanceof EAttribute ){ multiplicity = roseNode.getAttributeValue("MOF", "rose2mof.multiplicity"); if (multiplicity == null) { multiplicity = roseNode.getStereotype(); // default } }else { multiplicity = roseNode.getStereotype(); } if (multiplicity != null) { bounded.add(eTypedElement); if (multiplicity.length() > 0 && Character.isLetter(multiplicity.charAt(0)) && !"n".equalsIgnoreCase(multiplicity)) return; StringTokenizer stringTokenizer = new StringTokenizer(multiplicity, ". \n\r\t"); switch (stringTokenizer.countTokens()) { case 1: { String bound = stringTokenizer.nextToken(); if (bound.equals("*") || bound.equalsIgnoreCase("n")) { eTypedElement.setUpperBound(-1); } else { try { int boundValue = Integer.parseInt(bound); if (boundValue > 0) { eTypedElement.setLowerBound(boundValue); eTypedElement.setUpperBound(boundValue); } else { warning(RoseImporterPlugin.INSTANCE.getString("_UI_BadMultiplicityFor_message", new Object []{ multiplicity, eTypedElement.getName() })); } } catch (NumberFormatException exception) { warning(RoseImporterPlugin.INSTANCE.getString("_UI_BadMultiplicityFor_message", new Object []{ multiplicity, eTypedElement.getName() })); } } break; } case 2: { String lowerBound = stringTokenizer.nextToken(); try { int lowerBoundValue = Integer.parseInt(lowerBound); if (lowerBoundValue >= 0) { String upperBound = stringTokenizer.nextToken(); if (upperBound.equals("*") || upperBound.equalsIgnoreCase("n")) { eTypedElement.setLowerBound(lowerBoundValue); eTypedElement.setUpperBound(-1); } else { int upperBoundValue = Integer.parseInt(upperBound); if (upperBoundValue <= 0 || lowerBoundValue > upperBoundValue) { warning(RoseImporterPlugin.INSTANCE.getString("_UI_BadMultiplicityFor_message", new Object []{ multiplicity, eTypedElement.getName() })); } else { eTypedElement.setLowerBound(lowerBoundValue); eTypedElement.setUpperBound(upperBoundValue); } } } else { warning(RoseImporterPlugin.INSTANCE.getString("_UI_BadMultiplicityFor_message", new Object []{ multiplicity, eTypedElement.getName() })); } } catch (NumberFormatException exception) { warning(RoseImporterPlugin.INSTANCE.getString("_UI_BadMultiplicityFor_message", new Object []{ multiplicity, eTypedElement.getName() })); } break; } default: { warning(RoseImporterPlugin.INSTANCE.getString("_UI_BadMultiplicityFor_message", new Object []{ multiplicity, eTypedElement.getName() })); } } } } /** * Maps the single, user-friendly Rose setting into accessor method suppression, via EcoreUtil. */ protected void setEStructuralFeatureVisibility(RoseNode roseNode, EStructuralFeature eStructuralFeature) { switch (roseNode.getVisibility()) { case RoseNode.VISIBILITY_NONE: EcoreUtil.setSuppressedVisibility(eStructuralFeature, EcoreUtil.GET, true); if (eStructuralFeature.isChangeable() && !eStructuralFeature.isMany()) { EcoreUtil.setSuppressedVisibility(eStructuralFeature, EcoreUtil.SET, true); } if (eStructuralFeature.isUnsettable()) { EcoreUtil.setSuppressedVisibility(eStructuralFeature, EcoreUtil.IS_SET, true); if (eStructuralFeature.isChangeable()) { EcoreUtil.setSuppressedVisibility(eStructuralFeature, EcoreUtil.UNSET, true); } } break; case RoseNode.VISIBILITY_READ_ONLY: if (eStructuralFeature.isMany()) { warning(RoseImporterPlugin.INSTANCE.getString("_UI_InvalidReadOnlyVisibility_message", new Object []{ eStructuralFeature.getName() })); } else if (eStructuralFeature.isChangeable()) { EcoreUtil.setSuppressedVisibility(eStructuralFeature, EcoreUtil.SET, true); } if (eStructuralFeature.isUnsettable()) { EcoreUtil.setSuppressedVisibility(eStructuralFeature, EcoreUtil.IS_SET, true); if (eStructuralFeature.isChangeable()) { EcoreUtil.setSuppressedVisibility(eStructuralFeature, EcoreUtil.UNSET, true); } } break; case RoseNode.VISIBILITY_READ_WRITE: if (!eStructuralFeature.isChangeable() && !eStructuralFeature.isMany()) { warning(RoseImporterPlugin.INSTANCE.getString( "_UI_InvalidReadWriteVisibility_message", new Object []{ eStructuralFeature.getName() })); } if (eStructuralFeature.isUnsettable()) { EcoreUtil.setSuppressedVisibility(eStructuralFeature, EcoreUtil.IS_SET, true); if (eStructuralFeature.isChangeable()) { EcoreUtil.setSuppressedVisibility(eStructuralFeature, EcoreUtil.UNSET, true); } } break; case RoseNode.VISIBILITY_READ_ONLY_UNSETTABLE: if (eStructuralFeature.isMany()) { warning(RoseImporterPlugin.INSTANCE.getString("_UI_InvalidReadOnlyVisibility_message", new Object []{ eStructuralFeature.getName() })); } else if (eStructuralFeature.isChangeable()) { EcoreUtil.setSuppressedVisibility(eStructuralFeature, EcoreUtil.SET, true); } if (!eStructuralFeature.isUnsettable()) { warning(RoseImporterPlugin.INSTANCE.getString( "_UI_InvalidUnsettableVisibility_message", new Object []{ eStructuralFeature.getName() })); } else if (eStructuralFeature.isChangeable()) { EcoreUtil.setSuppressedVisibility(eStructuralFeature, EcoreUtil.UNSET, true); } break; case RoseNode.VISIBILITY_READ_WRITE_UNSETTABLE: if (!eStructuralFeature.isChangeable()) { warning(RoseImporterPlugin.INSTANCE.getString( "_UI_InvalidReadWriteVisibility_message", new Object []{ eStructuralFeature.getName() })); } if (!eStructuralFeature.isUnsettable()) { warning(RoseImporterPlugin.INSTANCE.getString( "_UI_InvalidUnsettableVisibility_message", new Object []{ eStructuralFeature.getName() })); } break; default: break; } } protected boolean setEEnumLiteralProperties(RoseNode roseNode, EEnumLiteral eEnumLiteral) { setEModelElementProperties(roseNode, eEnumLiteral); String value = roseNode.getInitV(); if (value != null && !value.equals("")) { eEnumLiteral.setValue(Integer.parseInt(value)); return true; } else return false; } protected void setEParameterProperties(RoseNode roseNode, EParameter eParameter) { /* String name = roseNode.getType(); for (ETypeParameter eTypeParameter : eParameter.getEOperation().getETypeParameters()) { if (eTypeParameter.getName().equals(name)) { EGenericType eGenericType = EcoreFactory.eINSTANCE.createEGenericType(); eGenericType.setETypeParameter(eTypeParameter); eParameter.setEGenericType(eGenericType); return; } } */ setETypedElementProperties(roseNode, eParameter); eParameter.setOrdered(roseNode.isOrdered(true)); eParameter.setUnique(roseNode.isUnique(true)); String quid = roseNode.getRoseRefId(); if (quid != null && !quid.equals("")) { quid = quid.substring(1, quid.length() - 1); TableObject tableObj = (TableObject)roseUtil.quidTable.get(quid); if (tableObj != null) { roseUtil.typeTable.put(eParameter, tableObj.getName()); } else { warning(RoseImporterPlugin.INSTANCE.getString("_UI_UnresolvedTypeIDFor_message", new Object []{ quid, eParameter.getEOperation().getName() })); roseUtil.typeTable.put(eParameter, "EObject"); } } else { String type = getQualifiedTypeName(eParameter, roseNode.getType()); if (type != null && !type.equals("")) { eParameter.setEGenericType(parseTemplateArgument(type)); } else { warning(RoseImporterPlugin.INSTANCE.getString("_UI_UnresolvedTypeNameFor_message", new Object []{ roseNode.getRoseSupplier(), eParameter.getEOperation().getName() })); roseUtil.typeTable.put(eParameter, "EObject"); } } } protected void setEReferenceDefaultMultiplicity(EReference eReference) { if (eReference.getEOpposite() == null || !eReference.getEOpposite().isContainment()) { eReference.setLowerBound(0); eReference.setUpperBound(-1); } } public void setEEnums() { for (Map.Entry<EEnum, String> entry : eEnums.entrySet()) { EEnum eEnum = entry.getKey(); if (eEnum.getELiterals().isEmpty()) { populateEEnumFromDocumentation(eEnum, entry.getValue()); } } } protected static Comparator<Object> eClassComparator = new Comparator<Object>() { @Override public int compare(Object o1, Object o2) { // Order first by number of features (descending) and then alphabetically (ascending) // EClass c1 = (EClass)(o1 instanceof EGenericType ? ((EGenericType)o1).getEClassifier() : o1); EClass c2 = (EClass)(o2 instanceof EGenericType ? ((EGenericType)o2).getEClassifier() : o2); int count1 = c1.getEAllAttributes().size() + c1.getEAllReferences().size(); int count2 = c2.getEAllAttributes().size() + c2.getEAllReferences().size(); if (count1 < count2) return 1; if (count1 > count2) return -1; return c1.getName().compareTo(c2.getName()); } }; public void setSuper() { Map<EClass, List<EGenericType>[]> superMap = new HashMap<EClass, List<EGenericType>[]>(); for (Iterator<Object> i = roseUtil.superTable.keySet().iterator(); i.hasNext();) { Object subObject = i.next(); if (subObject instanceof EClass) { EClass eClass = (EClass)subObject; List<EGenericType> extend = new ArrayList<EGenericType>(); List<EGenericType> unspecified = new ArrayList<EGenericType>(); List<EGenericType> mixin = new ArrayList<EGenericType>(); List<EGenericType> nonClass = new ArrayList<EGenericType>(); for (Iterator<String> j = roseUtil.superTable.get(eClass).iterator(); j.hasNext();) { String quid = j.next(); String stereotype = j.next(); TableObject tableObject = (TableObject)roseUtil.quidTable.get(quid); if (tableObject != null) { Object superObject = tableObject.getObject(); if (superObject instanceof EClass) { EClass superClass = (EClass)superObject; EGenericType eGenericType = EcoreFactory.eINSTANCE.createEGenericType(); eGenericType.setEClassifier(superClass); if (stereotype != null) { int start = stereotype.indexOf("<"); if (start != -1) { if (stereotype.endsWith(">")) { String templateArguments = stereotype.substring(start + 1, stereotype.length() - 1); eGenericType.getETypeArguments().addAll(parseTemplateArguments(templateArguments)); } stereotype = stereotype.substring(0, start); } } if (!superClass.isInterface()) { if ("extend".equals(stereotype)) { extend.add(eGenericType); } else if ("mixin".equals(stereotype)) { mixin.add(eGenericType); } else { unspecified.add(eGenericType); } } else { nonClass.add(eGenericType); } } else { warning(RoseImporterPlugin.INSTANCE.getString("_UI_CannotAddSuperLinkBetween_message", new Object []{ eClass.getName(), ((ENamedElement)superObject).getName() })); } } } if (extend.size() > 1) { warning(RoseImporterPlugin.INSTANCE.getString("_UI_CannotSpecifyMoreThanOneExtendFor_message", new Object []{ eClass.getName() })); } @SuppressWarnings("unchecked") List<EGenericType>[] lists = new List[]{extend, unspecified, mixin}; superMap.put(eClass, lists); eClass.getEGenericSuperTypes().addAll(extend); eClass.getEGenericSuperTypes().addAll(unspecified); eClass.getEGenericSuperTypes().addAll(mixin); eClass.getEGenericSuperTypes().addAll(nonClass); /* eClass.getESuperTypes().addAll(extend); eClass.getESuperTypes().addAll(unspecified); eClass.getESuperTypes().addAll(mixin); eClass.getESuperTypes().addAll(nonClass); */ } else { warning(RoseImporterPlugin.INSTANCE.getString( "_UI_CannotAddSuperLinkInvolving_message", new Object []{ ((ENamedElement)subObject).getName() })); } } sortSuper(superMap); } protected void sortSuper(Map<EClass, List<EGenericType>[]> superMap) { for (Map.Entry<EClass, List<EGenericType>[]> entry : superMap.entrySet()) { EClass eClass = entry.getKey(); List<EGenericType>[] collections = entry.getValue(); Collections.sort(collections[0], eClassComparator); Collections.sort(collections[1], eClassComparator); Collections.sort(collections[2], eClassComparator); List<EGenericType> combined = new UniqueEList<EGenericType>(collections[0]); combined.addAll(collections[1]); combined.addAll(collections[2]); EList<EGenericType> eSuper = eClass.getEGenericSuperTypes(); for (ListIterator<EGenericType> ordered = combined.listIterator(); ordered.hasNext();) { EGenericType eSuperItem = ordered.next(); eSuper.move(ordered.previousIndex(), eSuperItem); } } } protected List<ETypeParameter> parseTemplateParameters(String templateParameters) { List<ETypeParameter> result = new ArrayList<ETypeParameter>(); int start = 0; int depth = 0; for (int i = 0, length = templateParameters.length(); i < length; ++i) { char character = templateParameters.charAt(i); switch (character) { case ' ': { if (start == i) { ++start; } break; } case '<': { ++depth; break; } case '>': { --depth; break; } case ',': { if (depth == 0) { result.add(parseTemplateParameter(templateParameters.substring(start, i).trim())); start = i + 1; } break; } } } result.add(parseTemplateParameter(templateParameters.substring(start).trim())); return result; } ETypeParameter parseTemplateParameter(String templateParameter) { ETypeParameter eTypeParameter = EcoreFactory.eINSTANCE.createETypeParameter(); int index = templateParameter.indexOf(" extends "); if (index == -1) { eTypeParameter.setName(templateParameter); } else { eTypeParameter.setName(templateParameter.substring(0, index).trim()); String bounds = templateParameter.substring(index + 9).trim(); for (StringTokenizer stringTokenizer = new StringTokenizer(bounds, "&"); stringTokenizer.hasMoreTokens(); ) { String templateArgument = stringTokenizer.nextToken().trim(); eTypeParameter.getEBounds().add(parseTemplateArgument(templateArgument)); } } return eTypeParameter; } protected List<EGenericType> parseTemplateArguments(String templateArguments) { List<EGenericType> result = new ArrayList<EGenericType>(); int start = 0; int depth = 0; for (int i = 0, length = templateArguments.length(); i < length; ++i) { char character = templateArguments.charAt(i); switch (character) { case ' ': { if (start == i) { ++ start; } break; } case '<': { ++depth; break; } case '>': { --depth; break; } case ',': { if (depth == 0) { result.add(parseTemplateArgument(templateArguments.substring(start, i).trim())); start = i + 1; } break; } } } result.add(parseTemplateArgument(templateArguments.substring(start).trim())); return result; } EGenericType parseTemplateArgument(String templateArgument) { EGenericType eGenericType = EcoreFactory.eINSTANCE.createEGenericType(); int index = 0; int length = templateArgument.length(); if (index < length) { if (templateArgument.charAt(index) == '?') { ++index; while (index < length && Character.isWhitespace(templateArgument.charAt(index))) { ++index; } if (templateArgument.indexOf("extends ") == index) { eGenericType.setEUpperBound(parseTemplateArgument(templateArgument.substring(index + 8).trim())); } else if (templateArgument.indexOf("super ") == index) { eGenericType.setELowerBound(parseTemplateArgument(templateArgument.substring(index + 6).trim())); } } else { index = templateArgument.indexOf('<', index); String name; if (index == -1) { name = templateArgument; } else { name = templateArgument.substring(0, index); eGenericType.getETypeArguments().addAll(parseTemplateArguments(templateArgument.substring(index + 1, length - 1))); } roseUtil.typeTable.put(eGenericType, name); } } return eGenericType; } public void setIDs(final EObject parent, EObject child) { new EcoreSwitch<Object>() { @Override public Object caseEPackage(EPackage ePackage) { return null; } @Override public Object caseEClassifier(EClassifier eClassifier) { return null; } @Override public Object caseEOperation(EOperation eOperation) { return null; } @Override public Object caseEParameter(EParameter eParameter) { return null; } @Override public Object caseEStructuralFeature(EStructuralFeature eStructuralFeature) { return null; } @Override public Object caseEEnumLiteral(EEnumLiteral eEnumLiteral) { return null; } @Override public Object defaultCase(EObject eObject) { for (EObject child : eObject.eContents()) { setIDs(eObject, child); } return this; } }.doSwitch(child); } public void validate(EObject object) { new EcoreSwitch<Object>() { @Override public Object caseEDataType(EDataType eDataType) { return validateEDataType(eDataType); } @Override public Object caseEEnum(EEnum eEnum) { return validateEEnum(eEnum); } @Override public Object caseEClass(EClass eClass) { return validateEClass(eClass); } @Override public Object defaultCase(EObject eObject) { for (EObject child : eObject.eContents()) { validate(child); } return this; } }.doSwitch(object); } protected Object validateEDataType(EDataType eDataType) { if (!(eDataType instanceof EEnum) && eDataType.getInstanceClassName() == null) { error(RoseImporterPlugin.INSTANCE.getString("_UI_DatatypeNotSetFor_message", new Object []{ eDataType.getName() })); eDataType.setInstanceClassName("java.lang.String"); } return null; } protected Object validateEEnum(EEnum eEnum) { for (Iterator<EEnumLiteral> literals = eEnum.getELiterals().iterator(); literals.hasNext();) { EEnumLiteral eEnumLiteral = literals.next(); for (EEnumLiteral otherLiteral : eEnum.getELiterals()) { if (eEnumLiteral == otherLiteral) { break; } else if (eEnumLiteral.getName().equalsIgnoreCase(otherLiteral.getName())) { error(RoseImporterPlugin.INSTANCE.getString("_UI_DuplicateLiteral_message", new Object []{ eEnumLiteral.getName(), eEnum.getName() })); literals.remove(); break; } } } return this; } protected Object validateEClass(EClass eClass) { List<EReference> oppositesToRemove = new ArrayList<EReference>(); for (Iterator<EStructuralFeature> features = eClass.getEStructuralFeatures().iterator(); features.hasNext();) { EStructuralFeature eStructuralFeature = features.next(); if (eStructuralFeature instanceof EAttribute) { EAttribute eAttribute = (EAttribute)eStructuralFeature; // Temporary WAS/WSAD migration option. // if (unsettablePrimitive) { try { EDataType eDataType = eAttribute.getEAttributeType(); if (eDataType instanceof EEnum || eDataType.getInstanceClass().isPrimitive()) { eAttribute.setUnsettable(true); } } catch (Exception e) { // Ignore } } for (EStructuralFeature otherFeature : eClass.getEAllStructuralFeatures()) { if (eAttribute == otherFeature) { break; } else if (eAttribute.getName().equalsIgnoreCase(otherFeature.getName())) { error(RoseImporterPlugin.INSTANCE.getString("_UI_DuplicateAttribute_message", new Object []{ eAttribute.getName(), eClass.getName() })); features.remove(); break; } else if (!eAttribute.getEAttributeType().isSerializable() && !eAttribute.isTransient() && !"org.eclipse.emf.ecore.util.FeatureMap$Entry".equals(eAttribute.getEAttributeType().getInstanceClassName())) { error(RoseImporterPlugin.INSTANCE.getString("_UI_TheAttributeShouldBeTransient_message", new Object []{ eAttribute.getName(), eAttribute.getEType().getName() })); break; } } } else { EReference eReference = (EReference)eStructuralFeature; EReference opposite = eReference.getEOpposite(); if (opposite != null) { if (opposite.eContainer() == null) { error(RoseImporterPlugin.INSTANCE.getString("_UI_AnAssociationHasADanglingEnd_message", new Object []{ opposite.getName(), eReference.getName() })); opposite = null; eReference.setEOpposite(null); } else if (opposite.isContainment()) { // A container must be transient. // eReference.setTransient(true); if (eReference.getUpperBound() != 1) { if (bounded.contains(eReference)) { error(RoseImporterPlugin.INSTANCE.getString("_UI_ContainerRelationUpperBound_message", new Object []{ opposite.getName(), eReference.getName() })); } eReference.setUpperBound(1); } } } if (eReference.isTransient() && !eReference.isVolatile() && opposite != null && !opposite.isTransient() && opposite.isResolveProxies() && !opposite.isContainment()) { error(RoseImporterPlugin.INSTANCE.getString("_UI_CrossDocumentBidirectionalTransient_message", new Object []{ opposite.getName(), eReference.getName() })); } for (EStructuralFeature otherFeature : eClass.getEAllStructuralFeatures()) { if (eReference == otherFeature) { break; } else if (eReference.getName().equalsIgnoreCase(otherFeature.getName())) { error(RoseImporterPlugin.INSTANCE.getString("_UI_DuplicateReference_message", new Object []{ eReference.getName(), eClass.getName() })); if (opposite != null) { oppositesToRemove.add(opposite); } features.remove(); break; } } if (!eReference.isContainer() && "java.util.Map$Entry".equals(eReference.getEType().getInstanceClassName())) { if (!eReference.isContainment() || !eReference.isMany()) { error(RoseImporterPlugin.INSTANCE.getString("_UI_MultiplicityManyContainmentIsAssumedFor_message", new Object []{ eReference.getName(), eClass.getName() })); eReference.setContainment(true); eReference.setUpperBound(-1); } } } } for (EReference opposite : oppositesToRemove) { EClass oppositeEClass = opposite.getEContainingClass(); if (oppositeEClass != null) { oppositeEClass.getEStructuralFeatures().remove(opposite); } } for (EOperation eOperation : eClass.getEOperations()) { EClassifier opType = eOperation.getEType(); if (opType instanceof EClass && "java.util.Map$Entry".equals(opType.getInstanceClassName())) { if (!eOperation.isMany()) { warning (RoseImporterPlugin.INSTANCE.getString ("_UI_MultiplicityManyIsAssumedForOperation_message", new Object [] { eOperation.getName(), eClass.getName() })); eOperation.setUpperBound(-1); } } for (EParameter eParameter : eOperation.getEParameters()) { EClassifier paramType = eParameter.getEType(); if (paramType instanceof EClass && "java.util.Map$Entry".equals(paramType.getInstanceClassName())) { if (!eParameter.isMany()) { warning (RoseImporterPlugin.INSTANCE.getString ("_UI_MultiplicityManyIsAssumedForParameter_message", new Object [] { eParameter.getName(), eOperation.getName(), eClass.getName() })); eParameter.setUpperBound(-1); } } } } if (eClass.getESuperTypes().size() > 1) { Iterator<EClass> superTypes = eClass.getESuperTypes().iterator(); superTypes.next(); while (superTypes.hasNext()) { EClass superType = superTypes.next(); superFeatureLoop: for (Iterator<EStructuralFeature> superFeatures = superType.getEAllStructuralFeatures().iterator(); superFeatures.hasNext();) { EStructuralFeature superFeature = superFeatures.next(); for (EStructuralFeature otherFeature : eClass.getEAllStructuralFeatures()) { if (superFeature == otherFeature) { break; } else if (superFeature.getName().equalsIgnoreCase(otherFeature.getName())) { error(RoseImporterPlugin.INSTANCE.getString("_UI_DuplicateFeatureInheritance_message", new Object []{ superFeature.getName(), eClass.getName(), superType.getName() })); superTypes.remove(); break superFeatureLoop; } } } } } if ("java.util.Map$Entry".equals(eClass.getInstanceClassName())) { EStructuralFeature keyFeature = eClass.getEStructuralFeature("key"); EStructuralFeature valueFeature = eClass.getEStructuralFeature("value"); if (keyFeature == null) { error(RoseImporterPlugin.INSTANCE.getString("_UI_ExpectingFeatureNamedKey_message", new Object []{ eClass.getName() })); eClass.setInstanceClassName(null); } if (valueFeature == null) { error(RoseImporterPlugin.INSTANCE.getString("_UI_ExpectingFeatureNamedValue_message", new Object []{ eClass.getName() })); eClass.setInstanceClassName(null); } } return this; } protected Comparator<EStructuralFeature> eStructuralFeatureComparator = new Comparator<EStructuralFeature>() { @Override public int compare(EStructuralFeature o1, EStructuralFeature o2) { return eStructuralFeatures.indexOf(o1) - eStructuralFeatures.indexOf(o2); } }; public void setEReferences() { // process eStructuralFeatures for association end(Role) // for (EReference eReference : roseUtil.refTable.keySet()) { String quid = roseUtil.refTable.get(eReference); TableObject tableObject = (TableObject)roseUtil.quidTable.get(quid); if (tableObject != null) { Object struct = tableObject.getObject(); if (struct instanceof EClass) { ((EClass)struct).getEStructuralFeatures().add( -1 - Collections.binarySearch(((EClass)struct).getEStructuralFeatures(), eReference, eStructuralFeatureComparator), eReference); } else { warning(RoseImporterPlugin.INSTANCE.getString("_UI_CannotAddReference_message", new Object []{ eReference.getName(), tableObject.getName() })); } } } for (Map.Entry<EStructuralFeature, String> entry : eStructuralFeatureToXMLNamespaceMap.entrySet()) { EStructuralFeature eStructuralFeature = entry.getKey(); if (eStructuralFeature.eContainer() != null) { ExtendedMetaData.INSTANCE.setNamespace(entry.getKey(), entry.getValue()); } } } public void setETypeClassifier() { // setup attribute and parameter type // for (EObject element : roseUtil.typeTable.keySet()) { String type = roseUtil.typeTable.get(element); int position = -1; if (element instanceof EAnnotation) { position = Integer.parseInt(((EAnnotation)element).getDetails().get("position")); element = ((EAnnotation)element).getReferences().get(0); } TableObject tableObj = null; ETypeParameter resolvedETypeParameter = null; if (type.indexOf(".") == -1) { String qualifier = ""; LOOP: for (EObject parent = element.eContainer(); parent != null; parent = parent.eContainer()) { if (parent instanceof EClass || parent instanceof EOperation) { for (ETypeParameter eTypeParameter : parent instanceof EClass ? ((EClass)parent).getETypeParameters() : ((EOperation)parent).getETypeParameters()) { if (type.equals(eTypeParameter.getName())) { resolvedETypeParameter = eTypeParameter; break LOOP; } } } if (parent instanceof EPackage) { qualifier = ((EPackage)parent).getName() + "." + qualifier; } } if (resolvedETypeParameter == null) { tableObj = (TableObject)roseUtil.nameTable.get(qualifier + type); } } if (resolvedETypeParameter == null && tableObj == null) { tableObj = (TableObject)roseUtil.nameTable.get(type); } EClassifier eType; if (tableObj != null && tableObj.getObject() != null && (element instanceof ETypedElement || element instanceof EGenericType)) { // Convert attributes of with EClass type to references. // eType = (EClassifier)tableObj.getObject(); } else if (resolvedETypeParameter == null) { // It was not found in the model class so check if primitive type. // eType = getBasicType(type); if (eType == null) { EObject eNamedElement = element; while (!(eNamedElement instanceof ENamedElement)) { eNamedElement = eNamedElement.eContainer(); } warning(RoseImporterPlugin.INSTANCE.getString("_UI_UnresolvedTypeNameFor_message", new Object []{ type, ((ENamedElement)eNamedElement).getName() })); eType = getBasicType("EString"); } } else { // TODO So what should be the eType be now? // eType = getBasicType("EString"); } EGenericType eGenericType = null; if (element instanceof EGenericType) { eGenericType = (EGenericType)element; if (resolvedETypeParameter == null) { eGenericType.setEClassifier(eType); } else { eGenericType.setETypeParameter(resolvedETypeParameter); } element = element.eContainer(); } if (element instanceof EAttribute && eType instanceof EClass || attributesToConvert.contains(element)) { EAttribute eAttribute = (EAttribute)element; EReference eReference = EcoreFactory.eINSTANCE.createEReference(); RoseNode roseNode = eModelElementToRoseNodeMap.remove(eAttribute); eReference.setName(eAttribute.getName()); eReference.setTransient(eAttribute.isTransient()); eReference.setVolatile(eAttribute.isVolatile()); eReference.setDerived(eAttribute.isDerived()); eReference.setChangeable(eAttribute.isChangeable()); eReference.setLowerBound(eAttribute.getLowerBound()); eReference.setUpperBound(eAttribute.getUpperBound()); eReference.setContainment(roseNode == null || !"by reference".equalsIgnoreCase(roseNode.getContainment())); eReference.setResolveProxies(false); eReference.getEAnnotations().addAll(eAttribute.getEAnnotations()); eReference.setUnsettable(eAttribute.isUnsettable()); eReference.setOrdered(eAttribute.isOrdered()); eReference.setUnique(eAttribute.isUnique()); eStructuralFeatures.set(eStructuralFeatures.indexOf(eAttribute), eReference); EClass containingClass = eAttribute.getEContainingClass(); containingClass.getEStructuralFeatures().add(containingClass.getEStructuralFeatures().indexOf(eAttribute), eReference); containingClass.getEStructuralFeatures().remove(eAttribute); element = eReference; } else if (element instanceof EReference) { // Convert reference to attribute if its type is an EDataType... // EReference eReference = (EReference)element; boolean convert = eType instanceof EDataType; // ...or if it's a wildcard or group feature. Also, make it FeatureMap-typed. // int kind = ExtendedMetaData.INSTANCE.getFeatureKind(eReference); if (kind == ExtendedMetaData.ATTRIBUTE_WILDCARD_FEATURE || kind == ExtendedMetaData.ELEMENT_WILDCARD_FEATURE || kind == ExtendedMetaData.GROUP_FEATURE) { convert = true; eType = EcorePackage.Literals.EFEATURE_MAP_ENTRY; } if (convert) { EAttribute eAttribute = EcoreFactory.eINSTANCE.createEAttribute(); eAttribute.setName(eReference.getName()); eAttribute.setTransient(eReference.isTransient()); eAttribute.setVolatile(eReference.isVolatile()); eAttribute.setDerived(eReference.isDerived()); eAttribute.setChangeable(eReference.isChangeable()); eAttribute.setLowerBound(eReference.getLowerBound()); eAttribute.setUpperBound(eReference.getUpperBound()); eAttribute.getEAnnotations().addAll(eReference.getEAnnotations()); eAttribute.setUnsettable(eReference.isUnsettable()); eAttribute.setOrdered(eReference.isOrdered()); eAttribute.setUnique(eReference.isUnique()); eStructuralFeatures.set(eStructuralFeatures.indexOf(eReference), eAttribute); EClass containingClass = eReference.getEContainingClass(); if (containingClass != null) { containingClass.getEStructuralFeatures().add(containingClass.getEStructuralFeatures().indexOf(eReference), eAttribute); containingClass.getEStructuralFeatures().remove(eReference); } element = eAttribute; } } if (element instanceof EDataType) { if (eGenericType == null) { ((EDataType)element).setInstanceClassName(eType.getInstanceClassName()); } } else if (position != -1) { List<EClassifier> exceptions = ((EOperation)element).getEExceptions(); if (!exceptions.contains(eType)) { if (position < exceptions.size()) { exceptions.add(position, eType); } else { exceptions.add(eType); } } } else if (element instanceof ETypedElement) { if (eGenericType != null) { if (!(element instanceof EOperation) || !((EOperation)element).getEGenericExceptions().contains(eGenericType)) { ((ETypedElement)element).setEGenericType(eGenericType); } } else { ((ETypedElement)element).setEType(eType); } if (element instanceof EStructuralFeature) { EStructuralFeature eStructuralFeature = (EStructuralFeature)element; if ("".equals(eStructuralFeature.getName())) { eStructuralFeature.setName(eType.getName()); } } } } } protected EClassifier getBasicType(String value) { if (value.equals("boolean") || value.equalsIgnoreCase("eboolean")) return EcorePackage.Literals.EBOOLEAN; else if (value.equalsIgnoreCase("boolean") || value.equalsIgnoreCase("ebooleanobject")) return EcorePackage.Literals.EBOOLEAN_OBJECT; else if (value.equalsIgnoreCase("string") || value.equalsIgnoreCase("estring")) return EcorePackage.Literals.ESTRING; else if (value.equalsIgnoreCase("char") || value.equalsIgnoreCase("echar")) return EcorePackage.Literals.ECHAR; else if (value.equalsIgnoreCase("character") || value.equalsIgnoreCase("echaracterobject")) return EcorePackage.Literals.ECHARACTER_OBJECT; else if (value.equals("double") || value.equalsIgnoreCase("edouble") || value.equalsIgnoreCase("currency")) return EcorePackage.Literals.EDOUBLE; else if (value.equalsIgnoreCase("double") || value.equalsIgnoreCase("edoubleobject")) return EcorePackage.Literals.EDOUBLE_OBJECT; else if (value.equalsIgnoreCase("int") || value.equalsIgnoreCase("eint")) return EcorePackage.Literals.EINT; else if (value.equalsIgnoreCase("integer") || value.equalsIgnoreCase("eintegerobject")) return EcorePackage.Literals.EINTEGER_OBJECT; else if (value.equals("long long") || value.equals("long") || value.equalsIgnoreCase("elong")) return EcorePackage.Literals.ELONG; else if (value.equalsIgnoreCase("long") || value.equalsIgnoreCase("elongobject")) return EcorePackage.Literals.ELONG_OBJECT; else if (value.equals("float") || value.equalsIgnoreCase("efloat") || value.equalsIgnoreCase("single")) return EcorePackage.Literals.EFLOAT; else if (value.equalsIgnoreCase("float") || value.equalsIgnoreCase("efloatobject")) return EcorePackage.Literals.EFLOAT_OBJECT; else if (value.equals("short") || value.equalsIgnoreCase("eshort")) return EcorePackage.Literals.ESHORT; else if (value.equalsIgnoreCase("short") || value.equalsIgnoreCase("eshortobject")) return EcorePackage.Literals.ESHORT_OBJECT; else if (value.equals("byte") || value.equalsIgnoreCase("ebyte")) return EcorePackage.Literals.EBYTE; else if (value.equals("byte[]") || value.equalsIgnoreCase("ebytearray") || value.equalsIgnoreCase("ebyte[]")) return EcorePackage.Literals.EBYTE_ARRAY; else if (value.equalsIgnoreCase("byte") || value.equalsIgnoreCase("ebyteObject")) return EcorePackage.Literals.EBYTE_OBJECT; else if (value.equalsIgnoreCase("ebigdecimal")) return EcorePackage.Literals.EBIG_DECIMAL; else if (value.equalsIgnoreCase("ebiginteger")) return EcorePackage.Literals.EBIG_INTEGER; else if (value.equalsIgnoreCase("edate")) return EcorePackage.Literals.EDATE; else if (value.equalsIgnoreCase("eobject")) return EcorePackage.Literals.EOBJECT; else if (value.equalsIgnoreCase("efeaturemapentry")) return EcorePackage.Literals.EFEATURE_MAP_ENTRY; else return null; } public void createEPackageForRootClasses(EList<EObject> extent, RoseNode roseNode, String packageName) { ArrayList<EObject> list = new ArrayList<EObject>(); for (EObject eObject : extent) { if (!(eObject instanceof EPackage)) { list.add(eObject); } } if (!list.isEmpty()) { EPackage ePackage = EcoreFactory.eINSTANCE.createEPackage(); addDelegateAnnotation(ePackage); setEPackageProperties(roseNode, ePackage, packageName.toLowerCase()); extent.add(ePackage); for (Iterator<EObject> i = list.iterator(); i.hasNext();) { EClassifier eClassifier = (EClassifier)i.next(); ePackage.getEClassifiers().add(eClassifier); extent.remove(eClassifier); } } } private void addDelegateAnnotation(EPackage packg){ EcoreUtil.setAnnotation(packg, ECORE_NS_URI, INVOCATION_DELEGATES, DELEGATE_URI); EcoreUtil.setAnnotation(packg, ECORE_NS_URI, VALIDATION_DELEGATES, DELEGATE_URI); } protected void build(RoseNode roseNode, Object parent, ENamedElement eNamedElement) { String quid = roseNode.getRoseId(); if (quid != null && !quid.equals("")) { quid = quid.substring(1, quid.length() - 1); } TableObject tableObj = (TableObject)roseUtil.quidTable.get(quid); if (tableObj != null) { tableObj.setObject(eNamedElement); } if (parent instanceof EPackage) { ((EPackage)parent).getEClassifiers().add((EClassifier)eNamedElement); } else if (parent instanceof EList<?>) { @SuppressWarnings("unchecked") EList<ENamedElement> namedElements = (EList<ENamedElement>)parent; namedElements.add(eNamedElement); } } protected String upperCaseName(String name) { return name != null && name.length() > 0 && Character.isLowerCase(name.charAt(0)) ? Character.toUpperCase(name.charAt(0)) + name.substring(1) : name; } protected String validName(String name) { return CodeGenUtil.validJavaIdentifier(name); } protected void warning(String message) { System.err.println("-->Warning: " + message); roseUtil.addDiagnostic(new BasicDiagnostic(Diagnostic.WARNING, RoseImporterPlugin.getPlugin().getBundle().getSymbolicName(), 0, message, null)); } protected void error(String message) { System.err.println("-->Error: " + message); roseUtil.addDiagnostic(new BasicDiagnostic(Diagnostic.ERROR, RoseImporterPlugin.getPlugin().getBundle().getSymbolicName(), 0, message, null)); } protected String getQualifiedTypeName(ETypedElement typedElement, String type) { return getQualifiedTypeName((EModelElement)typedElement, type); } protected String getQualifiedTypeName(EModelElement eModelElement, String type) { // try to retrieve the fully qualified name of the specified type... if (null == type || type.length() == 0 || "void".equals(type)) return type; String qualifiedType = type; // convert to dot-separated format if necessary... if (qualifiedType.indexOf("::") != -1) { StringTokenizer st = new StringTokenizer(qualifiedType, "::"); if (st.hasMoreTokens()) { st.nextToken(); } StringBuffer stringBuffer = new StringBuffer(); while (st.hasMoreTokens()) { // remove garbage characters... stringBuffer.append(st.nextToken().replace('"', ' ').replace('[', ' ').replace(']', ' ').trim()); if (st.hasMoreTokens()) { stringBuffer.append("."); } } qualifiedType = stringBuffer.toString(); } // qualify type name if not already qualified... if (qualifiedType.indexOf('.') == -1 && eModelElement != null) { String qualifier = ""; for (EObject parent = eModelElement.eContainer(); null != parent; parent = parent.eContainer()) { if (parent instanceof EPackage) { qualifier = ((EPackage)parent).getName() + "." + qualifier; } } qualifiedType = qualifier + qualifiedType; } if (!qualifiedType.equals(type) && !roseUtil.nameTable.containsKey(qualifiedType)) { qualifiedType = type; } return qualifiedType; } }